package com.bindatax.core.meta;


import com.bindatax.core.util.PropertiesUtil;
import lombok.Getter;
import lombok.Setter;

import java.util.Properties;

@Getter
@Setter
public class TaskMeta {

    public final static String BUSINESS_ATTR_PREFIX = "biz.";//具体业务属性前缀
    public final static String key_logDriver = "db.log.driver";
    public final static String key_logUrl = "db.log.url";
    public final static String key_logUser = "db.log.user";
    public final static String key_logPwd = "db.log.pwd";
    public final static String key_logSchema = "db.log.schema";
    public final static String key_logValidationQuery = "db.log.validationQuery";
    public final static String key_sourceDriver = "db.source.driver";
    public final static String key_sourceUrl = "db.source.url";
    public final static String key_sourceUser = "db.source.user";
    public final static String key_sourcePwd = "db.source.pwd";
    public final static String key_sourceSchema = "db.source.schema";
    public final static String key_sourceValidationQuery = "db.source.validationQuery";
    public final static String key_targetDriver = "db.target.driver";
    public final static String key_targetUrl = "db.target.url";
    public final static String key_targetUser = "db.target.user";
    public final static String key_targetPwd = "db.target.pwd";
    public final static String key_targetSchema = "db.target.schema";
    public final static String key_targetValidationQuery = "db.target.validationQuery";


    public final static String key_querySql= "db.query.sql";
    public final static String key_querySchema = "db.query.schema";
    public final static String key_queryIncrementTimeField = "db.query.field.incrementTimeName";
    public final static String key_queryTotal= "db.query.total";

    public final static String key_targetTableName = "db.target.table.name";
    public final static String key_targetKeys = "db.target.field.key.names";
    public final static String key_targeAutoCheckKey = "db.target.field.key.autoCheck";

    public final static String key_writeSegmentNumber = "trans.write.segment.number";
    public final static String key_writeSegmentBatchSize = "trans.write.segment.batch.size";
    public final static String key_writeAwaitOutTime = "trans.write.await.outTime";
    public final static String key_errorIgnore = "trans.error.ignore.continue";
    public final static String key_logOutErrorMaxSize = "trans.log.out.error.ignore.maxSize";
    public final static String key_openTotalStatistics = "trans.statistics.open";
    public final static String key_failTryNum = "trans.fail.try.num";
    public final static String key_failTryInterval = "trans.fail.try.interval";
    public final static String key_writeSplitDuplicatePrimary = "trans.write.split.duplicate.primary";

    // 日志数据库相关参数设置
    private String logDriver;
    private String logUrl;
    private String logUser;
    private String logPwd;
    private String logSchema;
    private String logValidationQuery;

    // 数据源驱动
    private String sourceDriver;
    private String sourceUrl;
    private String sourceUser;
    private String sourcePwd;
    private String sourceSchema;
    private String sourceValidationQuery;

    // 目标数据库驱动
    private String targetDriver;
    private String targetUrl;
    private String targetUser;
    private String targetPwd;
    private String targetSchema;
    private String targetValidationQuery;

    private String querySql;//查询SQL语句
    private String querySchema;//如果不填写，则使用源库schema
    private String queryIncrementTimeField;//源表增量时间字段
    private String targetTableName;//目标表名
    private String targetKeys;//主键名或联合字段（英文逗号间隔）

    private boolean targeAutoCheckKey;//当targetKeys为空时，是否自动检测主键

    private int writeSegmentNumber;//入库数据分片数
    private int writeSegmentBatchSize;//提交批次大小
    private int writeAwaitOutTime;//分片入库超时时间（秒）
    private boolean errorIgnore;//是否忽略入库错误
    private int logOutErrorMaxSize;//日志输出错误最多多少条
    private boolean openTotalStatistics;//是否开启总数统计
    private int failTryNum;//错误入库后尝试入库次数
    private int failTryInterval;//数据入库失败后，重试入库的时间间隔
    private boolean writeSplitDuplicatePrimary;//数据入库失败后，重试入库的时间间隔
    private boolean queryTotal;//是否查询总数

    private Properties pros;


    public TaskMeta(Properties pros){
        readPros(pros);
    }

    public void readPros(Properties pros){
        this.pros = pros;
        this.logDriver = PropertiesUtil.get(pros,key_logDriver,"");
        this.logUrl = PropertiesUtil.get(pros,key_logUrl,"");
        this.logUser = PropertiesUtil.get(pros,key_logUser,"");
        this.logPwd = PropertiesUtil.get(pros,key_logPwd,"");
        this.logSchema = PropertiesUtil.get(pros,key_logSchema,"");
        this.logValidationQuery = PropertiesUtil.get(pros,key_logValidationQuery,"");

        // 数据源驱动
        this.sourceDriver = PropertiesUtil.get(pros,key_sourceDriver,"");
        this.sourceUrl = PropertiesUtil.get(pros,key_sourceUrl,"");
        this.sourceUser = PropertiesUtil.get(pros,key_sourceUser,"");
        this.sourcePwd = PropertiesUtil.get(pros,key_sourcePwd,"");
        this.sourceSchema = PropertiesUtil.get(pros,key_sourceSchema,"");
        this.sourceValidationQuery = PropertiesUtil.get(pros,key_sourceValidationQuery,"");

        // 目标数据库驱动
        this.targetDriver = PropertiesUtil.get(pros,key_targetDriver,"");
        this.targetUrl = PropertiesUtil.get(pros,key_targetUrl,"");
        this.targetUser = PropertiesUtil.get(pros,key_targetUser,"");
        this.targetPwd = PropertiesUtil.get(pros,key_targetPwd,"");
        this.targetSchema = PropertiesUtil.get(pros,key_targetSchema,"");
        this.targetValidationQuery = PropertiesUtil.get(pros,key_targetValidationQuery,"");


        this.querySql = PropertiesUtil.get(pros,key_querySql,"");//查询SQL语句
        this.querySchema = PropertiesUtil.get(pros,key_querySchema,this.sourceSchema);//如果不填写，则使用源库schema
        this.queryIncrementTimeField = PropertiesUtil.get(pros,key_queryIncrementTimeField,"");//源表增量时间字段
        this.targetTableName = PropertiesUtil.get(pros,key_targetTableName,"");//目标表名
        this.targetKeys = PropertiesUtil.get(pros,key_targetKeys,"");//主键名或联合字段（英文逗号间隔）

        this.targeAutoCheckKey = PropertiesUtil.get(pros,key_targeAutoCheckKey,true);//当bizTargetKeys为空时，是否自动检测主键
        this.writeSegmentNumber = PropertiesUtil.get(pros,key_writeSegmentNumber,3);//入库数据分片数
        this.writeSegmentBatchSize = PropertiesUtil.get(pros,key_writeSegmentBatchSize,2000);//提交批次大小
        this.writeAwaitOutTime = PropertiesUtil.get(pros,key_writeAwaitOutTime,0);//分片入库超时时间（秒）
        this.errorIgnore = PropertiesUtil.get(pros,key_errorIgnore,false);//是否忽略入库错误
        this.logOutErrorMaxSize = PropertiesUtil.get(pros,key_logOutErrorMaxSize,10);//日志输出错误最多多少条
        this.openTotalStatistics = PropertiesUtil.get(pros,key_openTotalStatistics,true);//是否开启总数统计
        this.failTryNum = PropertiesUtil.get(pros,key_failTryNum,3);//错误入库后尝试入库次数
        this.failTryInterval = PropertiesUtil.get(pros,key_failTryInterval,3);//数据入库失败后，重试入库的时间间隔
        //数据入库之前，是否需要检测并拆分同一个提交批次内，是否存在重复主键数据。
        this.writeSplitDuplicatePrimary = PropertiesUtil.get(pros,key_writeSplitDuplicatePrimary,false);
        this.queryTotal = PropertiesUtil.get(pros,key_queryTotal,false);
    }

    public void addBizValue(String code,String value){
        pros.put(BUSINESS_ATTR_PREFIX + code , value);
    }

    public String getBizValue(String code){
        return pros.getProperty(BUSINESS_ATTR_PREFIX + code);
    }

}
